#include <iostream>
#include <pthread.h>
#include <unistd.h>
#include <queue>

#define MIX_NUM 5
template <class T>
class Blockqueue
{
public:
    //构造函数
    Blockqueue(int cap = MIX_NUM)
        :_capcity(cap)
    {
        pthread_mutex_init(&_mutex, NULL);
        pthread_cond_init(&_empty, NULL);
        pthread_cond_init(&_full, NULL);
    }
    //析构
    ~Blockqueue()
    {
        pthread_mutex_destroy(&_mutex);
        pthread_cond_destroy(&_empty);
        pthread_cond_destroy(&_full);
    }
    //判空
    bool Empty()
    {
        return _q.empty();
    }
    //判满
    bool Full()
    {
        return _q.size() == _capcity;
    }
    //插入数据（生产者生产数据）
    void Push(const T& data)
    {
        pthread_mutex_lock(&_mutex);
        while(Full())
        {
            //当资源满的时候，就要等待
            pthread_cond_wait(&_full, &_mutex);
        }
        _q.push(data);
        pthread_mutex_unlock(&_mutex);
        pthread_cond_signal(&_empty);
    }
    //删除数据（消费者消费数据）
    void Pop(T& data)
    {
        pthread_mutex_lock(&_mutex);
        while(Empty())
        {
            //当没有资源的时候，阻塞
            pthread_cond_wait(&_empty,&_mutex);
        }
        data = _q.front();
        _q.pop();
        pthread_mutex_unlock(&_mutex);
        pthread_cond_signal(&_full);
    }
private:
    std::queue<T> _q;
    int _capcity;
    pthread_mutex_t _mutex;
    pthread_cond_t _empty;
    pthread_cond_t _full;
};